import pyserv, sys

# Adding response headers to this list will put them in any response that doesn't need specific headers.
DEFAULT_RESPONSE_HEADERS = dict(Server=pyserv.VERSION)

class TestServ(pyserv.HTTPServer):
	def __init__(self):
		# Initialize base class.
		super().__init__()
		# Register GET and POST methods.
		self.register("GET",self.do_GET)
		self.register("POST",self.do_POST)
		# Add registries for other reasons
		self.contents = dict()
		self.mime = dict()
		self.cgi = dict()
		self.post = dict()
		# Add index.html content to be statically served.
		with open("index.html") as f:
			self.registerPage("/",[l.rstrip() for l in f],"text/html")
			self.registerPage("/index.html",self.contents["/"],"text/html")
		# Register greeting form (from bottom of index.html) as POST /.
		self.registerPost("/",self.greetingform)

	def registerPage(self,path,content,mime="text/plain"):
		self.contents[path] = content
		self.mime[path] = mime

	def registerCGI(self,path,func):
		self.cgi[path]=func

	def registerPost(self,path,func):
		self.post[path] = func

	def greetingform(self,path,headers,data):
		with open("greetings.html") as f:
			return 200, DEFAULT_RESPONSE_HEADERS, [l.rstrip().format(pyserv.lazySan(data['name'][0])) for l in f]

	def do_GET(self,method,path,headers):
		resp_headers = dict(Server=pyserv.VERSION)
		contents = []
		if not path.startswith("/cgi/"): # CGI paths are relative to /cgi/.
			try:
				contents = self.contents[path] # Get static path.
				resp_headers["Content-Type"] = self.mime[path]
			except:
				return pyserv.abort(404)
		else:
			try:
				contents = self.cgi[path[len("/cgi"):]](path,headers) # Run CGI page function.
			except IndexError:
				return pyserv.abort(404) # If path doesn't exist, we want to return 404
			except:
				return pyserv.abort(500) # If something else happens, it's an internal error.
		return self.formatResponse(200,resp_headers,contents) # Send contents along.

	def do_POST(self,m,path,headers,data):
		if path in self.post:
			try:
				# CGI functions return response code, response headers, and contents.
				respcode, resp_headers, contents = self.post[path](path,headers,pyserv.unquote(data))
				# This data is directly passed into formatResponse to get a formatted response.
				return self.formatResponse(respcode,resp_headers,contents)
			except pyserv.Abort404: # Abort404 error is a signal
				return pyserv.abort(404)
			except: # If something else goes wrong, it's an internal error.
				return pyserv.abort(500)
		return pyserv.abort(405) # If path isn't in self.post, we aren't going to bother asking GET for it.
